package org.springframework.extcache;

import java.util.concurrent.Callable;

import org.springframework.cache.Cache;
import org.springframework.cache.CacheManager;

public abstract class AbstractCacheManager implements CacheManager, ExpireableCacheManager, FusibleCacheManager {

  private boolean isFused = false;
  private int     expireTime;

  @Override
  public Cache getCache(String name) {
    if (isFused()) {
      return new NoneCache(name, this);
    }
    ConfigurableCache cache = doGetCache(name);
    return cache;
  }

  protected abstract ConfigurableCache doGetCache(String name);

  public void setIsFused(boolean isFused) {
    this.isFused = isFused;
  }

  /**
   * 无缓存，使用空的cache，让spring cache组件短路，提升性能。
   * 
   * @version 1.0.0
   * @author zhangz8@yeah.net
   * @date 2019年12月19日上午10:09:19
   */
  protected static class NoneCache extends AbstractConfiggurableCache {

    NoneCache(String name, CacheManager cacheManager) {
      this.name = name;
      this.setCacheManager(cacheManager);
    }

    @Override
    public boolean isLoaded() {
      return false;
    }

    @Override
    public String getVersion() {
      return null;
    }

    @Override
    public void setVersion(String version) {
    }

    @Override
    public Object getNativeCache() {
      return null;
    }

    @Override
    public ValueWrapper get(Object key) {
      return null;
    }

    @Override
    public <T> T get(Object key, Class<T> type) {
      return null;
    }

    @Override
    public <T> T get(Object key, Callable<T> valueLoader) {
      return null;
    }

    @Override
    public void put(Object key, Object value) {
    }

    @Override
    public ValueWrapper putIfAbsent(Object key, Object value) {
      return null;
    }

    @Override
    public void evict(Object key) {
    }

    @Override
    public void clear() {
    }

  }

  @Override
  public int getExpireTime() {
    return expireTime;
  }

  public boolean getIsFused() {
    return isFused;
  }

  public void setExpireTime(int expireTime) {
    this.expireTime = expireTime;
  }

}
